package com.leyantech.ecp.agenx.web.handler;

import com.leyantech.ai.DialogueManagerGrpc.DialogueManagerBlockingStub;
import com.leyantech.ai.DialogueQuestion;
import com.leyantech.ecp.agenx.common.config.Constants;
import com.leyantech.ecp.agenx.common.converter.input.DialogueQuestionConverter;
import com.leyantech.ecp.agenx.common.converter.output.DialogueReplyConverter;

import com.google.inject.Inject;
import io.opentracing.Scope;
import io.opentracing.Span;
import io.opentracing.util.GlobalTracer;
import io.vertx.core.Handler;
import io.vertx.core.http.HttpHeaders;
import io.vertx.core.http.HttpServerResponse;
import io.vertx.core.json.JsonObject;
import io.vertx.ext.auth.impl.jose.JWT;
import io.vertx.ext.web.RoutingContext;
import io.vertx.tracing.opentracing.OpenTracingUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;

/**
 * @author eahau, {@literal <eahau@foxmail.com>}
 * @date 2022-10-31.
 */
@Slf4j
public class TestWindowHandler implements Handler<RoutingContext> {

  private final DialogueManagerBlockingStub dialogueManagerStub;

  private final DialogueQuestionConverter dialogueQuestionConverter;

  private final DialogueReplyConverter dialogueReplyConverter;

  @Inject
  public TestWindowHandler(DialogueManagerBlockingStub dialogueManagerStub,
      DialogueQuestionConverter dialogueQuestionConverter,
      DialogueReplyConverter dialogueReplyConverter) {
    this.dialogueManagerStub = dialogueManagerStub;
    this.dialogueQuestionConverter = dialogueQuestionConverter;
    this.dialogueReplyConverter = dialogueReplyConverter;
  }

  @Override
  public void handle(RoutingContext context) {
    final JsonObject body = context.body().asJsonObject();

    final String jwtToken = context.request().getHeader(HttpHeaders.AUTHORIZATION);

    if (StringUtils.isBlank(jwtToken)) {
      context.fail(404);
      return;
    }

    final String token = jwtToken.substring(jwtToken.indexOf(' ') + 1);

    final JsonObject payload = JWT.parse(token).getJsonObject("payload");

    final String sid = payload.getString(Constants.STORE_ID_FIELD);
    final String nick = payload.getString("nick");

    body.put("sid", sid);
    body.put("user_nick", nick);

    final DialogueQuestion dialogueQuestion = dialogueQuestionConverter.apply(body);

    final HttpServerResponse response = context.response().setChunked(true);

    final Span span = OpenTracingUtil.getSpan();

    try (final Scope ignored = GlobalTracer.get().scopeManager().activate(span)) {
      dialogueManagerStub.blockingQuestion(dialogueQuestion).forEachRemaining(dialogueReply -> {
        final JsonObject reply = dialogueReplyConverter.apply(dialogueReply);
        response.write(reply.toBuffer());
      });
      response.end();
    } catch (Exception e) {
      log.error("blockingQuestion onError", e);
      response.end(e.getMessage());
    }

  }

  public void warmup() {
    final JsonObject body = new JsonObject("{\n"
        + "    \"sid\":\"191781350\",\n"
        + "    \"user_nick\":\"warmup\",\n"
        + "    \"content\":\"回复\",\n"
        + "    \"test_win_mode\":1\n"
        + "}"
    );

    for (int i = 0; i < 10; i++) {
      try {
        final DialogueQuestion dialogueQuestion = dialogueQuestionConverter.apply(body);
        dialogueManagerStub.blockingQuestion(dialogueQuestion);
      } catch (Exception ignore) {
      }
    }
  }

}
